package web_mapper

import (
	"context"
	"gorm.io/gorm"
	"sync"
	"transport/web/web_model"
	"transport/web/web_vo"
)

type TransBillMapper struct {
	DB   *gorm.DB
	Ctx  context.Context
	Lock *sync.RWMutex
}

func (mapper *TransBillMapper) Create(m *web_model.TransBill) (ret *web_model.TransBill, err error) {
	mapper.Lock.Lock()
	defer mapper.Lock.Unlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Create(m).Error; err != nil {
		return nil, err
	}
	return m, nil
}

func (mapper *TransBillMapper) Update(m *web_model.TransBill) (ret *web_model.TransBill, err error) {
	mapper.Lock.Lock()
	defer mapper.Lock.Unlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Model(&web_model.TransBill{}).Where("id = ?", m.ID).Updates(m).Error; err != nil {
		return nil, err
	}
	return m, nil
}
func (mapper *TransBillMapper) UpdateArrivedOkStatus(billSn, status string) (err error) {
	mapper.Lock.Lock()
	defer mapper.Lock.Unlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Model(&web_model.TransBill{}).Where("trans_bill.sn = ?", billSn).
		Where("NOT EXISTS ( SELECT trans_order.id FROM trans_order WHERE trans_bill.id = trans_order.trans_bill_id AND trans_order.status != '3' )").Update("status", status).Error; err != nil {
		return err
	}
	return nil
}
func (mapper *TransBillMapper) CreateOrUpdate(m *web_model.TransBill) (ret *web_model.TransBill, err error) {
	mapper.Lock.Lock()
	defer mapper.Lock.Unlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Model(m).Save(m).Error; err != nil {
		return nil, err
	}
	return m, nil
}
func (mapper *TransBillMapper) QueryById(id int64) (m *web_model.TransBill, err error) {
	mapper.Lock.RLock()
	defer mapper.Lock.RUnlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Model(&web_model.TransBill{}).Where("id = ?", id).First(&m).Error; err != nil {
		return nil, err
	}
	return m, nil
}
func (mapper *TransBillMapper) QueryByIds(ids []int64) (m []*web_model.TransBill, err error) {
	mapper.Lock.RLock()
	defer mapper.Lock.RUnlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Model(&web_model.TransBill{}).Where("id IN ?", ids).Find(&m).Error; err != nil {
		return nil, err
	}
	return m, nil
}
func (mapper *TransBillMapper) DeleteById(id int64) (err error) {
	mapper.Lock.Lock()
	defer mapper.Lock.Unlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Unscoped().Where("id = ?", id).Delete(&web_model.TransBill{}).Error; err != nil {
		return err
	}
	return nil
}

func (mapper *TransBillMapper) DeleteByIds(ids []int64) (err error) {
	mapper.Lock.Lock()
	defer mapper.Lock.Unlock()
	if err := mapper.DB.WithContext(mapper.Ctx).Unscoped().Where("id IN ?", ids).Delete(&web_model.TransBill{}).Error; err != nil {
		return err
	}
	return nil
}

func (mapper *TransBillMapper) Page(pageIndex, pageSize int, sn, carrierId, carId, driverId, status string) (items []*web_model.TransBill, count int64, err error) {
	mapper.Lock.RLock()
	defer mapper.Lock.RUnlock()
	var countTmp int64 = 0
	table := mapper.DB.WithContext(mapper.Ctx)
	if sn != "" {
		table = table.Where("sn like ?", "%"+sn+"%")
	}
	if carrierId != "" {
		table = table.Where("carrier_id = ?", carrierId)
	}
	if carId != "" {
		table = table.Where("car_id = ?", carId)
	}
	if driverId != "" {
		table = table.Where("driver_id = ?", driverId)
	}
	if status != "" {
		table = table.Where("status = ?", status)
	}
	if err := table.Order("created_at desc").Offset((pageIndex - 1) * pageSize).Limit(pageSize).Find(&items).Offset(-1).Limit(-1).Count(&countTmp).Error; err != nil {
		return nil, 0, err
	}
	return items, countTmp, nil
}
func (mapper *TransBillMapper) PageApp(pageIndex, pageSize int, tabIndex string) (items []*web_vo.TransBillPageRet, count int64, err error) {
	mapper.Lock.RLock()
	defer mapper.Lock.RUnlock()
	var countTmp int64 = 0
	table := mapper.DB.WithContext(mapper.Ctx).Table("trans_bill").Select("trans_bill.*,strftime('%Y-%m-%d %H:%M:%S',created_at,'localtime') as f_created_at")
	if tabIndex != "" {
		switch tabIndex {
		case "0":
			table = table.Where("status = ?", "1")
			break
		case "1":
			table = table.Where("status = ?", "2")
			break
		case "2":
			table = table.Where("status = ?", "3")
			break
		case "3":
			table = table.Where("status = ?", "4")
			break
		}
	}
	if err := table.Order("created_at desc").Offset((pageIndex - 1) * pageSize).Limit(pageSize).Find(&items).Offset(-1).Limit(-1).Count(&countTmp).Error; err != nil {
		return nil, 0, err
	}
	return items, countTmp, nil
}
func (mapper *TransBillMapper) List() (items []*web_model.TransBill, count int64, err error) {
	mapper.Lock.RLock()
	defer mapper.Lock.RUnlock()
	var countTmp int64 = 0
	table := mapper.DB.WithContext(mapper.Ctx)
	if err := table.Find(&items).Offset(-1).Limit(-1).Count(&countTmp).Error; err != nil {
		return nil, 0, err
	}
	return items, countTmp, nil
}
